// gamewidget.cpp
#include "gamewidget.h"

GameWidget::GameWidget(QWidget *parent) : QWidget(parent) {
    setFixedSize(WIDTH, HEIGHT);
    setFocusPolicy(Qt::StrongFocus);

    timer = new QTimer(this);
    connect(timer, &QTimer::timeout, this, &GameWidget::gameLoop);

    initGame();
    gameSpeed = 200; // 初始速度200ms
    timer->start(gameSpeed);


    QSoundEffect *eatSound = new QSoundEffect(this);
    eatSound->setSource(QUrl::fromLocalFile(":/music.wmv"));
    eatSound->play();
}

void GameWidget::initGame() {
    snake.length = 3;
    snake.x[0] = (WIDTH / 2 / BLOCK_SIZE) * BLOCK_SIZE;
    snake.y[0] = (HEIGHT / 2 / BLOCK_SIZE) * BLOCK_SIZE;
    snake.dir = RIGHT;

    for (int i = 1; i < snake.length; ++i) {
        snake.x[i] = snake.x[i-1] - BLOCK_SIZE;
        snake.y[i] = snake.y[i-1];
    }

    spawnFood();
    score = 0;
}

// 生成随机类型的食物
void GameWidget::spawnFood() {
    bool onSnake;
    do {
        onSnake = false;
        foodX = (QRandomGenerator::global()->bounded(WIDTH / BLOCK_SIZE)) * BLOCK_SIZE;
        foodY = (QRandomGenerator::global()->bounded(HEIGHT / BLOCK_SIZE)) * BLOCK_SIZE;

        // 随机选择食物类型（普通70%，其他各10%）
        int type = QRandomGenerator::global()->bounded(100);
        if (type < 70)       currentFoodType = NORMAL;
        else if (type < 80)  currentFoodType = FAST;
        else if (type < 90)  currentFoodType = SLOW;
        else                 currentFoodType = DOUBLE;

        // 检查是否与蛇身重叠
        for (int i = 0; i < snake.length; ++i) {
            if (foodX == snake.x[i] && foodY == snake.y[i]) {
                onSnake = true;
                break;
            }
        }
    } while (onSnake);
}

// 根据食物类型应用效果
void GameWidget::applyFoodEffect(FoodType type) {
    switch (type) {
    case NORMAL:
        score += 10;
        break;
    case FAST:
        score += 10;
        gameSpeed = qMax(50, gameSpeed - 40); // 加速20%（200->160）
        timer->start(gameSpeed);
        break;
    case SLOW:
        score += 10;
        gameSpeed = qMin(400, gameSpeed + 40); // 减速20%（200->240）
        timer->start(gameSpeed);
        break;
    case DOUBLE:
        score += 20;
        break;
    }
    gameSpeed = qMax(50, qMin(400, gameSpeed)); // 限制在50ms~400ms之间

}

// 获取食物颜色
QColor GameWidget::getFoodColor(FoodType type) {
    switch (type) {
    case NORMAL: return Qt::red;
    case FAST:   return Qt::cyan;
    case SLOW:   return Qt::blue;
    case DOUBLE: return Qt::magenta;
    default:     return Qt::red;
    }
}

void GameWidget::paintEvent(QPaintEvent *) {
    QPainter painter(this);

    // 绘制背景
    painter.fillRect(0, 0, width(), height(), Qt::black);

    // 绘制蛇
    for (int i = 0; i < snake.length; ++i) {
        painter.setBrush(i == 0 ? Qt::yellow : Qt::green);
        painter.drawRect(snake.x[i], snake.y[i], BLOCK_SIZE, BLOCK_SIZE);
    }

    // 绘制食物（根据类型设置颜色）
    painter.setBrush(getFoodColor(currentFoodType));
    painter.drawRect(foodX, foodY, BLOCK_SIZE, BLOCK_SIZE);

    // 绘制得分和速度
    painter.setPen(Qt::white);
    painter.setFont(QFont("Arial", 14));
    painter.drawText(10, 20, QString("得分: %1").arg(score));
    painter.drawText(10, 40, QString("速度: %1%").arg(20000/gameSpeed)); // 显示百分比

    QString typeText;
    switch(currentFoodType) {
    case FAST:   typeText = "加速!"; break;
    case SLOW:   typeText = "减速!"; break;
    case DOUBLE: typeText = "双倍!"; break;
    }
    painter.drawText(foodX, foodY-5, typeText);

}

void GameWidget::keyPressEvent(QKeyEvent *event) {
    switch (event->key()) {
    case Qt::Key_Up:    if (snake.dir != DOWN) snake.dir = UP; break;
    case Qt::Key_Down:  if (snake.dir != UP) snake.dir = DOWN; break;
    case Qt::Key_Left:  if (snake.dir != RIGHT) snake.dir = LEFT; break;
    case Qt::Key_Right: if (snake.dir != LEFT) snake.dir = RIGHT; break;
    case Qt::Key_Space: timer->isActive() ? timer->stop() : timer->start(gameSpeed); break; // 空格暂停
    case Qt::Key_Escape: qApp->quit(); break;
    }
}

void GameWidget::moveSnake() {
    for (int i = snake.length-1; i > 0; --i) {
        snake.x[i] = snake.x[i-1];
        snake.y[i] = snake.y[i-1];
    }

    switch (snake.dir) {
    case UP:    snake.y[0] -= BLOCK_SIZE; break;
    case DOWN:  snake.y[0] += BLOCK_SIZE; break;
    case LEFT:  snake.x[0] -= BLOCK_SIZE; break;
    case RIGHT: snake.x[0] += BLOCK_SIZE; break;
    case STOP:  break;
    }

    // 边界检测（穿墙）
    if (snake.x[0] >= WIDTH) snake.x[0] = 0;
    else if (snake.x[0] < 0) snake.x[0] = WIDTH - BLOCK_SIZE;
    if (snake.y[0] >= HEIGHT) snake.y[0] = 0;
    else if (snake.y[0] < 0) snake.y[0] = HEIGHT - BLOCK_SIZE;
}

void GameWidget::checkCollision() {
    // 食物碰撞
    if (snake.x[0] == foodX && snake.y[0] == foodY) {
        applyFoodEffect(currentFoodType); // 应用食物效果
        snake.length++;                   // 蛇身增长
        spawnFood();                      // 生成新食物
    }

    // 自碰撞检测
    for (int i = 2; i < snake.length; ++i) {
        if (snake.x[0] == snake.x[i] && snake.y[0] == snake.y[i]) {
            QMessageBox::information(this, "Game Over", QString("得分: %1").arg(score));
            initGame();
            timer->start(gameSpeed);
            return;
        }
    }
}

void GameWidget::gameLoop() {

    moveSnake();
    checkCollision();
    update();
}
